using System;
using System.IO;
using System.Net;
using System.Text;
using System.Xml;
using System.Xml.Serialization;

namespace Microsoft.Services.TfsAlert.Core
{
    public partial class ApplicationHelpers
    {
        public virtual Uri BuildFullAddress()
        {
            const string sitePath = "TFSAlert";

            UriBuilder addressBuilder = this.BuildBaseAddress();
            addressBuilder.Path = sitePath;

            return addressBuilder.Uri;
        }

        public UriBuilder BuildBaseAddress()
        {
            int port = int.Parse ( System.Configuration.ConfigurationManager.AppSettings["port"] );

            UriBuilder baseAddressUriBuilder = new UriBuilder();
            baseAddressUriBuilder.Host = this.getIpAddress();
            baseAddressUriBuilder.Port = port;

            return baseAddressUriBuilder;
        }

        private string getIpAddress()
        {
            string IPAddress = null;
            string hostName = Dns.GetHostName();
            
            IPHostEntry local = Dns.GetHostEntry( hostName );

            //TODO: @CPS Right now we just grab the first valid IPv4 address and return.  I assume this will be a problem with IPv6
            foreach (IPAddress ipAddress in local.AddressList )
            {
                if (ipAddress.AddressFamily == System.Net.Sockets.AddressFamily.InterNetwork)
                {
                    IPAddress = ipAddress.ToString();
                    break;
                }
            }
                
            return IPAddress;
        }

        public string GetTFSDataFilePath()
        {
            StringBuilder _builder = new StringBuilder();

            _builder.Append(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData));
            _builder.Append(@"\Microsoft\TfsAlert\");
            _builder.Append("TfsAlert.xml");

            return _builder.ToString();
        }

        public string GetTFSProfilePath()
        {
            StringBuilder _builder = new StringBuilder();

            _builder.Append(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData));
            _builder.Append(@"\Microsoft\TfsAlert\");

            return _builder.ToString();
        }

        public T DeserializeXml<T>( string XmlBlob )
        {
            XmlDocument xmlDocument = new XmlDocument();
            xmlDocument.LoadXml( XmlBlob );

            T eventObject = this.DeserializeXml<T>( xmlDocument );

            return eventObject;
        }

        public T DeserializeXml<T>( XmlDocument xmlDocument )
        {
            XmlNodeReader xmlNodeReader = new XmlNodeReader( xmlDocument );

            XmlSerializerFactory xmlSerializerFactory = new XmlSerializerFactory();
            XmlSerializer serializer = xmlSerializerFactory.CreateSerializer( typeof( T ) );

            T eventObject = (T)serializer.Deserialize( xmlNodeReader );

            return eventObject;
        }

        public string SerializeXml<T>( T objectToSerialize )
        {
            XmlSerializerFactory xmlSerializerFactory = new XmlSerializerFactory();
            XmlSerializer eventSerializer = xmlSerializerFactory.CreateSerializer( typeof( T ) );

            MemoryStream objStream = new MemoryStream();

            eventSerializer.Serialize( objStream, objectToSerialize );

            return this.getStringFromStream( objStream );
            ;
        }

        private string getStringFromStream( MemoryStream memoryStream )
        {
            memoryStream.Position = 0;
            byte[] byteArray = memoryStream.ToArray();
            Encoding Encoder = Encoding.UTF8;
            string returnValue = Encoder.GetString( byteArray );
            return returnValue;
        }
    }
}